# -*- coding: utf-8 -*-
"""
    moe.utils.inflection
    ~~~~~~~~~~~~~~~~~~~~

    String inflection functions.

    :copyright: 2009 by tipfy.org.
    :license: BSD, see LICENSE.txt for more details.
"""
import re
import unicodedata

from tipfy.utils import _unicode


def normalize(string):
    string = _unicode(string)
    return unicodedata.normalize('NFKD', string).encode('ascii', 'ignore')


def to_dashes(string):
    """Returns a string converted to use dashes with only lowercase
    alphanumerics.
    """
    string = normalize(string).lower()
    # Replace whitespaces by a dash.
    string = re.sub('\s+', '-', string)
    # Remove all non-alphanumeric chars.
    string = re.sub('[^a-z0-9-]', '', string)
    # Remove double dashes and strip them from the string start and end.
    return re.sub('-+', '-', string).strip('-')


def to_under(string):
    """Returns a string converted to use dashes with only lowercase
    alphanumerics.
    """
    string = normalize(string).lower()
    # Replace whitespaces by a underscore.
    string = re.sub('\s+', '_', string)
    # Remove all non-alphanumeric chars.
    string = re.sub('[^a-z0-9_]', '', string)
    # Remove double underscores and strip them from the string start and end.
    return re.sub('_+', '_', string).strip('_')


def to_camel(string):
    """Converts a string to CamelCase using only alphanumerics: "foo bar",
    "foo-bar" or "foo_bar" are converted to "FooBar".
    """
    string = normalize(string)
    string = re.sub('[^A-Za-z0-9]', ' ', string).strip()
    return ''.join(part[0].upper() + part[1:] for part in string.split(' '))


def camel_to_dashes(string):
    """Converts "camelCapsWord" and "CamelCapsWord" to "camel-caps-word"."""
    string = normalize(string)
    string = re.sub('([a-z0-9])([A-Z])', '\\1-\\2', string).strip().lower()
    res = re.sub('-+', '-', string)
    return to_dashes(res)


def camel_to_under(string):
    """Converts "camelCapsWord" and "CamelCapsWord" to "camel_caps_word"."""
    string = normalize(string)
    string = re.sub('([a-z0-9])([A-Z])', '\\1_\\2', string).strip().lower()
    res = re.sub('_+', '_', string)
    return to_under(res)
